Don't rename a directory to a directory
authorAlex Crichton <alex@alexcrichton.com>
Tue, 22 Jul 2014 17:21:27 +0000 (10:21 -0700)
committerAlex Crichton <alex@alexcrichton.com>
Tue, 22 Jul 2014 17:21:27 +0000 (10:21 -0700)
Test by @EdShaw!

Closes #227

src/cargo/ops/cargo_rustc/mod.rs
tests/test_cargo_compile.rs

index bba7072b2a18476ee828879d4974e9ac8fa938b0..6c63d4ad227b3c348d47ba9c3ceffc4b2c239fc1 100644 (file)
@@ -94,8 +94,9 @@ fn compile<'a, 'b>(targets: &[&'a Target], pkg: &'a Package,
     //
     // TODO: Should this be on the target or the package?
     let mut build_cmds = Vec::new();
-    for build_cmd in pkg.get_manifest().get_build().iter() {
-        build_cmds.push(try!(compile_custom(pkg, build_cmd.as_slice(), cx)));
+    for (i, build_cmd) in pkg.get_manifest().get_build().iter().enumerate() {
+        build_cmds.push(try!(compile_custom(pkg, build_cmd.as_slice(),
+                                            cx, i == 0)));
     }
 
     // After the custom command has run, execute rustc for all targets of our
@@ -136,18 +137,13 @@ fn compile<'a, 'b>(targets: &[&'a Target], pkg: &'a Package,
 }
 
 fn compile_custom(pkg: &Package, cmd: &str,
-                  cx: &Context) -> CargoResult<Job> {
+                  cx: &Context, first: bool) -> CargoResult<Job> {
     // TODO: this needs to be smarter about splitting
     let mut cmd = cmd.split(' ');
     // TODO: this shouldn't explicitly pass `false` for dest/deps_dir, we may
     //       be building a C lib for a plugin
     let layout = cx.layout(false);
     let output = layout.native(pkg);
-    if !output.exists() {
-        try!(fs::mkdir(&output, UserRWX).chain_error(|| {
-            internal("failed to create output directory for build command")
-        }));
-    }
     let mut p = util::process(cmd.next().unwrap())
                      .cwd(pkg.get_root())
                      .env("OUT_DIR", Some(&output))
@@ -157,6 +153,11 @@ fn compile_custom(pkg: &Package, cmd: &str,
         p = p.arg(arg);
     }
     Ok(Job::new(proc() {
+        if first {
+            try!(fs::mkdir(&output, UserRWX).chain_error(|| {
+                internal("failed to create output directory for build command")
+            }));
+        }
         try!(p.exec_with_output().map(|_| ()).map_err(|e| e.mark_human()));
         Ok(Vec::new())
     }))
index 5a5529bc3328c0b7ac2d0081d4dc2553d032691e..4497f24c01a5a84499d9e2aec94056cc28055303 100644 (file)
@@ -4,7 +4,7 @@ use std::path;
 use std::str;
 
 use support::{ResultTest, project, execs, main_file, basic_bin_manifest};
-use support::{COMPILING, RUNNING};
+use support::{COMPILING, RUNNING, cargo_dir};
 use hamcrest::{assert_that, existing_file};
 use cargo;
 use cargo::util::{process, realpath};
@@ -801,6 +801,42 @@ test!(custom_build_in_dependency {
                 execs().with_status(0));
 })
 
+// tests that custom build in dep can be built twice in a row - issue 227
+test!(custom_build_in_dependency_twice {
+    let p = project("foo")
+        .file("Cargo.toml", r#"
+            [project]
+
+            name = "foo"
+            version = "0.5.0"
+            authors = ["wycats@example.com"]
+
+            [[bin]]
+            name = "foo"
+            [dependencies.bar]
+            path = "./bar"
+            "#)
+        .file("src/foo.rs", r#"
+            extern crate bar;
+            fn main() { bar::bar() }
+            "#)
+        .file("bar/Cargo.toml", format!(r#"
+            [project]
+
+            name = "bar"
+            version = "0.0.1"
+            authors = ["wycats@example.com"]
+            build = '{}'
+        "#, "echo test"))
+        .file("bar/src/lib.rs", r#"
+            pub fn bar() {}
+        "#);
+    assert_that(p.cargo_process("cargo-build"),
+                execs().with_status(0));
+    assert_that(p.process(cargo_dir().join("cargo-build")),
+                execs().with_status(0));
+})
+
 // this is testing that src/<pkg-name>.rs still works (for now)
 test!(many_crate_types_old_style_lib_location {
     let mut p = project("foo");